#ifndef __EEPROM_HPP__
#define __EEPROM_HPP__

#include <iostream>
#include <string>

extern "C"
{
#include <rtthread.h>
#include <rtdevice.h>
#include "drv_spi.h"
#include <math.h>
}

typedef enum
{
    EEPROM_word_addr_bit_8,
    EEPROM_word_addr_bit_16,
    EEPROM_word_addr_bit_24,
    EEPROM_word_addr_bit_32,
} EEPROM_word_addr_bit;//字地址位数

//EEPROM_A2A1A0_mode与EEPROM_identity_code +读写位共同构成device address
typedef enum
{
    EEPROM_A2A1A0_mode_0_0_0 = 0,
    EEPROM_A2A1A0_mode_0_0_1 = 1,
    EEPROM_A2A1A0_mode_0_1_0 = 2,
    EEPROM_A2A1A0_mode_0_1_1 = 3,
    EEPROM_A2A1A0_mode_1_0_0 = 4,
    EEPROM_A2A1A0_mode_1_0_1 = 5,
    EEPROM_A2A1A0_mode_1_1_0 = 6,
    EEPROM_A2A1A0_mode_1_1_1 = 7
} EEPROM_A2A1A0_mode;//Ax管脚状态

//设备地址中除去Ax位的位
typedef enum
{
    EEPROM_identity_code_BL24C512A_normal = 0xA,
    EEPROM_identity_code_AT24C02_normal = 0xA,
} EEPROM_identity_code;

typedef enum
{
    EEPROM_status_ok,
    EEPROM_status_fail,
} EEPROM_status;

//支持芯片：
//
/*
 BL24C512A
 芯片重要细节：
 1、I2C地址位 1010 A2 A1 A0 W/R
 2、页写入模式注意：写一个超过128B的数据时单页，写满128B数据会返回到该页第一字节数据处继续覆写
 3、字节写入模式注意：写入后需要等待Twr时间
 4、WP低电平可读可写
 5、最高1M工作频率
 6、初步认为连续写操作只能连续写一个页的数据，读操作可以读取到末端

 AT24C02
 1、一个页只有8B
 2、其余与BL24C512A相同
 */

class EEPROM
{
private:
    std::string soft_i2c_name;
    struct rt_i2c_bus_device *soft_i2c;

    rt_base_t wp_pin; //wp_pin 使用GET_PIN()方式传入参数

    EEPROM_word_addr_bit word_addr_bit;
    uint32_t bytes_per_page;
    uint32_t total_bytes_num;
    uint8_t basic_device_address; //无读写位的设备地址，即A0为最低位
    uint8_t word_addr_temp[4];

    rt_mutex_t bus_lock;
    uint8_t debug_flag; //0 close 1 open
    EEPROM_status init_flag;

    void EEPROM_transfer_u32_to_4_u8_temp(uint32_t u32);
public:
    //wp_pin 使用GET_PIN()方式传入参数
    EEPROM(rt_base_t wp_pin,
           std::string soft_i2c_name,
           uint32_t bytes_per_page,
           uint32_t total_bytes_num,
           EEPROM_identity_code identity_code,
           EEPROM_A2A1A0_mode A2A1A0_mode,
           EEPROM_word_addr_bit word_addr_bit);

    void EEPROM_open_debug(); //打开调试模式
    void EEPROM_close_debug(); //关闭调试模式
    EEPROM_status EEPROM_get_status();
    uint32_t EEPROM_get_bytes_per_page();
    uint32_t EEPROM_get_total_bytes_num();
    uint32_t EEPROM_get_total_pages_num();

    void EEPROM_init_device();
    EEPROM_status EEPROM_write(uint32_t write_addr, uint8_t* write_buff, uint32_t write_size);
    EEPROM_status EEPROM_read(uint32_t read_addr, uint8_t* read_buff, uint32_t read_size);

};

#endif //__LTC6803_2_HPP__
